#include "kernel.h"
#include "global.h"

/*Message Envelope class member function*/
MsgEnv::MsgEnv(){
    sender_pid=target_pid=num_clock_ticks=0;
    type=0;
    next=NULL;
}

/*Message Envelope Queue Member Functions*/
MsgEnvQ::MsgEnvQ(){
    head=tail=NULL;size=0;
    return;
}

MsgEnvQ::MsgEnvQ(int NumOfNodes){
    head=tail=NULL;
    size=0;
    if (NumOfNodes>0){
        MsgEnv *cur;
        cur=new MsgEnv;
        head=tail=cur;
        cur->next=0;
        size++;
        while (size<NumOfNodes){
            cur=new MsgEnv;
            tail->next=cur;
            tail=cur;
            cur->next=0;
            size++; 
        }
    }
    return;
}

void MsgEnvQ::enqueue(MsgEnv * newNode){
    if (size==0){
        head=newNode;
        tail=newNode;
        size++;
        return;
    }
    tail->next=newNode;
    tail=newNode;	  
    newNode->next=0;
    size++;
    //cout << "enqueue!";
    return;
}

MsgEnv * MsgEnvQ::dequeue(){
    MsgEnv * temp;
    if (this->size == 0|| this->head==0){
            //cout << "its empty !";
            return 0;
    }		
    temp=head;
    head=temp->next;
    temp->next=0;
    size--;
    //cout << "dequeue!";
    return temp;
}

int MsgEnvQ::getsize(){//count number of nodes in the queue
    return size;
}

/*Class PCB member functions*/
PCB::PCB(){
    pid=priority=status=0;
    msgQ=NULL;
    next=NULL;
    address=NULL;
}

/*Class PCBQ member functions*/
PCBQ::PCBQ(){
    head=tail=NULL;
    size=0;
}

//not tested yet
void PCBQ::enqueue(PCB * newNode){
    if (size==0){
        head=newNode;
        tail=newNode;
        size++;
        return;
    }
    tail->next=newNode;
    tail=newNode;	  
    newNode->next=NULL;
    size++;
    //cout << "enqueue!";
    return;
}

PCB * PCBQ::dequeue(){
	PCB * temp;
	if (this->size == 0|| this->head==0){
		//cout << "its empty !";
		return 0;
	}		
	temp=head;
	head=temp->next;
	temp->next=NULL;
	size--;
	//cout << "dequeue!";
	return temp;
}


PCB * PCBQ::remqueue(int target_pid){
	PCB * temp,* prev;
        prev=this->head;
        temp=this->head;
        while(temp != NULL){
            if(temp->pid==target_pid){
                prev->next=temp->next;
                temp->next=NULL;
                size--;
                return temp;
            }
            else{
                prev=prev->next;
                temp=prev->next;
            }                
        }
        return NULL;
}

int PCBQ::getsize(){//count number of nodes in the queue
		return size;
}
